from django.shortcuts import render

pc_geetest_id = "5e876edb2bda195c265416b70e7389a7"
pc_geetest_key = "c1f0f6f5958507924d187db31cd136e5"
# Create your views here.
from luffyapi.libs.geetest import GeetestLib
from rest_framework.response import Response
from .utils import get_user_by_account
from rest_framework import status as http_status
from rest_framework.views import APIView
class CaptchaAPIView(APIView):
    """验证码视图类"""
    status = False
    user_id = 0
    def get(self,request):
        """获取验证码"""
        username = request.query_params.get("username")
        user = get_user_by_account(username)
        if user is None:
            return Response({"message":"对不起，用户不存在！"},status=http_status.HTTP_400_BAD_REQUEST)

        self.user_id = user.id
        gt = GeetestLib(pc_geetest_id, pc_geetest_key)
        self.status = gt.pre_process(self.user_id)
        # todo 后面增加status和user_id保存到redis数据库
        response_str = gt.get_response_str()
        return Response(response_str)

    def post(self,request):
        """验证码的验证方法"""
        gt = GeetestLib(pc_geetest_id, pc_geetest_key)
        challenge = request.POST.get(gt.FN_CHALLENGE, '')
        validate = request.POST.get(gt.FN_VALIDATE, '')
        seccode = request.POST.get(gt.FN_SECCODE, '')
        if self.status:
            result = gt.success_validate(challenge, validate, seccode, self.user_id)
        else:
            result = gt.failback_validate(challenge, validate, seccode)
        result = {"status":"success"} if result else {"status":"fail"}
        return Response(result)



from .models import User
#drf中满足 接收验证、保存数据需要用 CreateAPIView
from rest_framework.generics import CreateAPIView
from .serializer import UserModelSerializer
class UserAPIView(CreateAPIView):
    """
        用户视图
        继承CreateAPIView，就不用写def post了
    """
    queryset = User.objects.all()
    #指定序列化器，之后验证用户提交数据
    serializer_class = UserModelSerializer


from rest_framework import status
class MobileAPIView(APIView):
    """
        手机号注册页面需要后端检查手机号是否存在
        如果不用序列化器，直接继承APIView
    """
    def get(self,request,mobile):
        """
            GET /user/mobile/<mobile>/
        """

        # 验证手机是否已经被注册过
        if get_user_by_account(mobile) is not None:
            return Response({"message":"手机号已经被注册"},status=status.HTTP_400_BAD_REQUEST)
        return Response({"message":"ok"})


from luffyapi.libs.yuntongxun.sms import YunTongXin
import random
from django_redis import get_redis_connection
from luffyapi.settings import constants
import logging,json
log = logging.getLogger("django")
class SMSCodeAPIView(APIView):  # 只是用第三方捷库，只需要对redis操作
    """
        发送短信
    """
    def get(self, request, mobile):
        """
            短信验证码
        """
        # 判断手机号码是否在60秒内发送过短信
        redis_conn = get_redis_connection('sms_code')  # 读取redis配置短信的 "sms_code" 配置部分
        ret = redis_conn.get("mobile_%s"%(mobile))
        #原理，如果第一次请求肯定是None，就不会触发下面的if，会生成验证码并存到redis中
        # 如果请求过来不是None，证明在发送间隔时间内 还没过期又发送，需要提示用户发送频繁请等待
        if ret is not None:
            return Response({"message":"对不起不能频繁发送"},status=status.HTTP_400_BAD_REQUEST)

        # 生成短信验证码 "%06d"不足6位数字前面补0
        sms_code = "%06d" % random.randint(1, 999999)

        # 保存短信验证码到redis 【使用事物将多条命令集中发送给redis，提高执行效率，一个错了全都不生效】
        #1，创建事物的管道对象pipe(装载事物所有的操作)
        pipe = redis_conn.pipeline()
        #2，开启事物
        pipe.multi()
        #3，对事物操作的步骤全部添加到管道中， redis_conn对象换成pipe对象
        pipe.setex("sms_%s"%(mobile),constants.SMS_EXPIRE_TIME,sms_code)  ## 存短信验证码的 数据 和 数据有效期 set k——手机号 过期时间  value  key标识每个用户有数据自己的key
        pipe.setex("mobile_%s"%(mobile),constants.SMS_INTERVAL_TIME,"_")  ## 存短信发送间隔的发送有效期value随便给，代表废弃，主要用过期时间功能
        #执行事物
        pipe.execute()

        # 调用短信sdk，发送短信
        try:
            from mycelery.sms.tasks import send_sms #导入任务函数
            send_sms.delay(mobile,sms_code)         #执行函数,参数通过delay(传递参数)

            """
                # 下面发送短信的逻辑放到了celery的tasks的任务中的send_sms函数里，需要传参mobile,sms_code，然后对task进行改造
                ccp=YunTongXin()
                ret = json.loads(ccp.run(mobile,sms_code))  #官方是分钟级别 需要转换时间并且//60拿到整数
                if ret.get('statusCode') != "000000":
                    log.error("用户手机号发送短信失败,手机号:%s" % (mobile))
                    return Response({"message": "发送短信失败！"}, status=status.HTTP_500_INTERNAL_SERVER_ERROR)
            """
        # 响应短信发送结果
        except:
            return Response({"message":"发送短信失败！"},status=status.HTTP_500_INTERNAL_SERVER_ERROR)

        return Response({"message": "发送短信成功！"})





from rest_framework.generics import ListAPIView
from order.models import Order
from .serializer import UserOrderModelSerializer
from rest_framework.permissions import IsAuthenticated
class UserOrderAPIView(ListAPIView):
    # queryset = Order.objects.all()    #拿着所有的，当加上权限验证时，需要单独定义获取的值
    serializer_class = UserOrderModelSerializer
    permission_classes = [IsAuthenticated]
    def get_queryset(self):
        """
            注释掉上面 # queryset = Order.objects.all()
            重写，因为涉及到用户id，还有权限验证
            根据用户来获取 用户对应的订单信息
        """
        return Order.objects.filter(user_id=self.request.user.id)







